package com.iqiyi.pps.epg.core.utils;

import com.iqiyi.pps.epg.api.model.web.program.TProgramTime;
import com.iqiyi.pps.epg.core.model.carousel.ProgramNode;
import com.iqiyi.pps.epg.core.model.carousel.ProgramNodeElement;
import com.iqiyi.pps.epg.core.model.program.ProgramData;

import java.util.ArrayList;
import java.util.List;

/**
 * Created by karkarrotxu on 2015/11/30.
 */
public final class ProgramDaySortUtil {
    private ProgramDaySortUtil() {
    }

    public static List<ProgramNodeElement> transToProgramNodeElementList(List<ProgramData> programDataList) {
        List<ProgramNodeElement> nodeElementList = new ArrayList<ProgramNodeElement>();
        ProgramNodeElement nodeElement = null;
        for (ProgramData temple : programDataList) {
            nodeElement = new ProgramNodeElement();
            nodeElement.setId(temple.getId());
            nodeElement.setAdvertDuration(temple.getAdvertDuration() * DateTimeUtil.SECOND);
            nodeElement.setStartPlayTime(temple.getStartPlayTime().getTime());
            nodeElement.setEndPlayTime(temple.getStopPlayTime().getTime());
            if (temple.getLive() != null) {
                nodeElement.setLive(temple.getLive().intValue());
            }

            if (nodeElement.isTypeLive() || temple.getIsLocked() == ProgramData.PROGRAM_LOCKED) {
                nodeElement.setDuration(nodeElement.getEndPlayTime() - nodeElement.getStartPlayTime());
            } else {
                nodeElement.setDuration(1000l * temple.getDuration());
            }

            nodeElement.setLockStatus(temple.getIsLocked());
            nodeElementList.add(nodeElement);
        }
        return nodeElementList;
    }

    public static List<ProgramNode> transToProgramNodeList(List<ProgramNodeElement> nodeElementList, long dayStartTime, long dayEndTime, long checkTime,long yesterdayEndTime) {
        List<ProgramNode> nodeList = new ArrayList<ProgramNode>();

        ProgramNode skipNode = new ProgramNode(ProgramNode.NODE_SKIP);
        skipNode.setStartTime(dayStartTime);
        long newEndTime = checkTime < yesterdayEndTime?yesterdayEndTime:checkTime;
        skipNode.setEndTime(newEndTime);
        ProgramNode lastNode = skipNode;
        nodeList.add(lastNode);
        for (ProgramNodeElement temp : nodeElementList) {
            if (temp.getAdvertStartTime() < checkTime) {
                skipNode.addSkipChild(temp);
            } else {
                if (lastNode.getNodeType() == ProgramNode.NODE_SKIP) {
                    ProgramNode newNode = new ProgramNode();
                    newNode.setStartTime(skipNode.getEndTime());
                    lastNode = newNode;
                    nodeList.add(lastNode);
                }
                if (temp.isTypeLive() || temp.getLockStatus() == ProgramData.PROGRAM_LOCKED) {
                    if (lastNode.getEndTime() > temp.getAdvertStartTime()) {
                        lastNode.addLiveChild(temp);
                    } else {
                        lastNode.setEndTime(temp.getAdvertStartTime());
                        ProgramNode newNode = new ProgramNode();
                        newNode.addLiveChild(temp);
                        lastNode = newNode;
                        nodeList.add(lastNode);
                    }
                }
            }
        }
        lastNode.setEndTime(dayEndTime);
        return nodeList;
    }

    public static void dealNodelList(List<ProgramNode> nodeList, List<ProgramNodeElement> nodeElementList, long dayEndTime) {

        int nodeElementLength = nodeElementList.size();
        int nodeLength = nodeList.size();
        int insertIndex = 1;

        ProgramNodeElement nodeElement = null;
        ProgramNode insertNode = null;

        ProgramNode overDayNode = new ProgramNode(ProgramNode.NODE_OVER_DAY);
        ProgramNode skipNode = nodeList.get(0);
        int overCount = 0;
        for (int i = skipNode.getChildren().size(); i < nodeElementLength; i++) {
            nodeElement = nodeElementList.get(i);
            if (!(nodeElement.isTypeLive() || nodeElement.getLockStatus() == ProgramData.PROGRAM_LOCKED)) {
                while (insertIndex < nodeLength) {
                    insertNode = nodeList.get(insertIndex);
                    if (!insertNode.addChild(nodeElement)) {
                        insertIndex++;
                    } else {
                        break;
                    }
                }
                if (insertIndex == nodeLength) {
                    if (overCount == 0) {
                        overCount++;
                        insertNode.addEndChild(nodeElement);
                    } else {
                        overDayNode.addEndChild(nodeElement);
                    }
                }
            }
        }
        nodeList.add(overDayNode);
    }

    public static List<TProgramTime> calculateTProgramTime(List<ProgramNode> nodeList, long dayEndTime) {
        long startTime = System.currentTimeMillis();
        long endTime = 0;
        long lastStartTime = 0;
        List<ProgramNodeElement> children = null;
        List<TProgramTime> moveList = new ArrayList<TProgramTime>();
        TProgramTime moveData = null;
        String startTimeString = null;
        String endTimeString = null;
        for (ProgramNode nodeTemple : nodeList) {
            if (nodeTemple.getNodeType() == ProgramNode.NODE_SKIP) {
                continue;
            }
            if (nodeTemple.getNodeType() == ProgramNode.NODE_OVER_DAY) {
                long newStartTime = lastStartTime + 1000;
                if (newStartTime > dayEndTime) {
                    newStartTime = dayEndTime;
                }
                if (nodeTemple.hasChildren()) {
                    children = nodeTemple.getChildren();
                    for (ProgramNodeElement elementChild : children) {
                        if (!(elementChild.isTypeLive() || elementChild.getLockStatus() == ProgramData.PROGRAM_LOCKED)) {
                            moveData = new TProgramTime();
                            moveData.setId(elementChild.getId());
                            startTimeString = newStartTime + "";
                            endTimeString = newStartTime + "";
                            moveData.setStartPlayTime(startTimeString);
                            moveData.setStopPlayTime(endTimeString);
                            moveData.setStartStreamTime(startTimeString);
                            moveData.setStopStreamTime(endTimeString);
                            moveList.add(moveData);
                        }
                    }
                }
                break;
            }
            startTime = nodeTemple.getStartTime();
            if (nodeTemple.hasChildren()) {
                children = nodeTemple.getChildren();
                for (ProgramNodeElement elementChild : children) {
                    if ((elementChild.isTypeLive() || elementChild.getLockStatus() == ProgramData.PROGRAM_LOCKED)) {
                        if (endTime < elementChild.getEndPlayTime()) {
                            endTime = elementChild.getEndPlayTime();
                        }
                    } else {
                        endTime = startTime + elementChild.getDuration() + elementChild.getAdvertDuration();
                        if (startTime != elementChild.getAdvertStartTime() || endTime != elementChild.getEndPlayTime()) {
                            moveData = new TProgramTime();
                            moveData.setId(elementChild.getId());
                            startTimeString = (startTime + elementChild.getAdvertDuration()) + "";
                            endTimeString = endTime + "";
                            moveData.setStartPlayTime(startTimeString);
                            moveData.setStopPlayTime(endTimeString);
                            moveData.setStartStreamTime(startTimeString);
                            moveData.setStopStreamTime(endTimeString);
                            moveList.add(moveData);
                        }
                    }
                    lastStartTime = startTime;
                    startTime = endTime;
                }
            }
        }
        return moveList;
    }

    public static boolean checkIsOverDay(ProgramData programData) {
        long startTime = programData.getStartPlayTime().getTime() - DateTimeUtil.SECOND * programData.getAdvertDuration();
        long endTime = programData.getStopPlayTime().getTime();
        return checkIsOverDay(startTime ,endTime);
    }

    public static boolean checkIsOverDay(long startTime,long endTime){
        return endTime - DateTimeUtil.getZeroTime(startTime)>= DateTimeUtil.DAY_TIME;
    }
}
